package com.java.portal.dal.dao.poem;

import java.util.List;

import org.apache.commons.lang.StringUtils;
import org.hibernate.Query;
import org.hibernate.Session;
import org.hibernate.SessionFactory;

import com.google.inject.Inject;
import com.java.portal.dal.util.HibernateUtil;

public class BaseDAO
{
	private final SessionFactory	sessionFactory;

	@Inject
	public BaseDAO()
	{
		this.sessionFactory = getSessionFactory();
	}

	protected SessionFactory getSessionFactory()
	{
		try
		{
			return (SessionFactory) HibernateUtil.getSessionFactory();
		} 
		catch (Throwable e)
		{
			throw new IllegalStateException("Could not locate SessionFactory in JNDI", e);
		}
	}

	public Session getSession()
	{
		return sessionFactory.getCurrentSession();
	}

	public void flushBatch()
	{
		getSession().flush();
		getSession().clear();
	}

	@SuppressWarnings("unchecked")
	public <T> T findById(long id, Class<T> clazz)
	{
		T instance = (T) getSession().get(clazz, id);
		return instance;
	}

	@SuppressWarnings("unchecked")
	public <T> T findByIntegrationId(String integrationId, Class<T> clazz)
	{
		T instance = null;

		Query query = getSession().createQuery("from " + clazz.getName() + " as o where o.integrationId = ?");
		query.setString(0, integrationId);

		List list = query.list();

		if (list.size() > 0)
		{
			instance = (T) list.get(0);
		}

		return instance;
	}

	public <T> T findById(long id, String integrationId, Class<T> clazz)
	{
		if (id > 0)
		{
			return findById(id, clazz);
		} else if (StringUtils.isNotBlank(integrationId))
		{
			return findByIntegrationId(integrationId, clazz);
		} else
		{
			return null;
		}
	}

	@SuppressWarnings("unchecked")
	public <T> T findByName(String name, Class<T> clazz)
	{
		T result = null;

		if (StringUtils.isNotBlank(name))
		{
			Query query = getSession().createQuery("from " + clazz.getName() + " as o where o.name = ?");
			query.setString(0, name);

			List list = query.list();

			if (list.size() > 0)
			{
				result = (T) list.get(0);
			}
		}

		return result;
	}

	@SuppressWarnings("unchecked")
	public <T> T merge(T detachedInstance)
	{
		T result = (T) getSession().merge(detachedInstance);

		return result;
	}
}
